#include <linux/init.h>
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/kobject.h>
#include <linux/sysfs.h>
#include <linux/slab.h>

/*
struct kobj_attribute {
    struct attribute attr;
    ssize_t (*show)(struct kobject *kobj, struct kobj_attribute *attr,
            char *buf);
    ssize_t (*store)(struct kobject *kobj, struct kobj_attribute *attr,
             const char *buf, size_t count);
};

#define __ATTR(_name,_mode,_show,_store) { \
    .attr = {.name = __stringify(_name), .mode = _mode },   \
    .show   = _show,                    \
    .store  = _store,                   \
}

retval = sysfs_create_files(&obj->kobj,(const struct attribute **)my_attrs);
if (retval) {
    // ...
} 

*/

static sszie_t my_show(struct kobject *kobj, struct kobj_attribute *attr, char *buf)
{
    return sprintf(buf, "test show\n");
}

static sszie_t my_show(struct kobject *kobj, struct kobj_attribute *attr, const char *buf, size_t count)
{
    char t_buf[513];
    if (count > 512)
        count = 512;
    memcpy(t_buf, buf, count);
    t_buf[count] = 0;
    printk("%s\n", t_buf);
    return count;
}

static struct kobj_attribute my_attr = __ATTR(led_status, 0660, led_status_show, led_status_store); //Doesn't support 0666 in new version.
static struct attribute *my_attrs[] = {
    &my_attr,
    NULL,
};


static struct kobject *kob;
static struct kset *kst;

static int __init sys_test_init(void)
{
    int ret = 0;
    kst = kset_create_and_add("test_kset", NULL, kernel_kobj->parent);
    if (!kst)
    {
        printk(KERN_ALERT "Create kset failed\n");
        kset_put(kst);
    }
    kob = kzalloc(sizeof(*kob), GFP_KERNEL);
    if (IS_ERR(kob))
    {
        printk(KERN_ALERT "alloc failed!!\n");
        return -ENOMEM;
    }

    ret = kobject_init_and_add(kob, NULL, NULL, "%s", "test_obj");
    if (ret)
    {
        kobject_put(kob);
        kset_unregister(kst);
    }

    printk(KERN_DEBUG "kobj test project!!!\n");
    return 0;
}

static void __exit sys_test_exit(void)
{
    kobject_put(kob);
    kset_unregister(kst);
    printk(KERN_DEBUG "goodbye !!!\n");
}

module_init(sys_test_init);
module_exit(sys_test_exit);

MODULE_AUTHOR("test@xx.com>");
MODULE_DESCRIPTION("Linux Kernel hello module");
MODULE_LICENSE("GPL");
